﻿using Microsoft.AspNetCore.Http;
using Model.DTO.Manager;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Text;
using System.Threading.Tasks;
using WPay.Domain.Base;
using WPay.Infrastructure.EFCore;
using WPay.Infrastructure.Unity;

namespace WPay.Domain.MainModule.Interface.RepositoryServices
{
    public interface IEfCore_RepositoryService : IRepository_IocServices
    {
        #region 异步
        /// <summary>
        /// 数据分页的方法
        /// </summary>
        /// <typeparam name="S"></typeparam>
        /// <param name="PageIndex">当前页码</param>
        /// <param name="PageSize">每页显示条数</param>
        /// <param name="specification">数据查询条件表达式</param>
        /// <param name="orderByExpression">排序的条件表达式</param>
        /// <param name="IsDESC">是否为倒序</param>
        /// <param name="AsNoTracking">DbContext是否不跟踪查询出的实体</param>
        /// <returns></returns>
        EntityList<T> FindAll<T>(int PageIndex, int PageSize, ISpecification<T> specification, System.Linq.Expressions.Expression<Func<T, T>> orderByExpression, bool IsDESC, bool? AsNoTracking = true, List<SortParms<T>> thenByExpression = null) where T : class, new();
        /// <summary>
        /// 得到所有数据
        /// </summary>
        /// <returns></returns>
        IEnumerable<T> GetAll<T>(bool? AsNoTracking = true) where T : class, new();

        /// <summary>
        /// 根据条件表达式取得相关数据
        /// </summary>
        /// <param name="specification">Lambda表达式</param>
        /// <returns></returns>
        IEnumerable<T> GetMany<T>(ISpecification<T> specification, bool? AsNoTracking = true) where T : class;

        /// <summary>
        /// 取得记录数
        /// </summary>
        /// <returns></returns>
        int GetCount<T>(bool configureAwait = true) where T : class;

        /// <summary>
        /// 根据条件取得记录数
        /// </summary>
        /// <param name="specification"></param>
        /// <returns></returns>
        int GetCount<T>(ISpecification<T> specification) where T : class;

        /// <summary>
        /// 根据条件表达式取得指定条数的数据
        /// </summary>
        /// <typeparam name="S"></typeparam>
        /// <param name="TopN">返回的数据条数</param>
        /// <param name="specification">Lambda表达式</param>
        /// <param name="orderByExpression">Lambda表达式</param>
        /// <param name="IsDESC"></param>
        /// <returns></returns>
        IEnumerable<T> GetListByTopN<S, T>(int TopN, ISpecification<T> specification, Expression<Func<T, S>> orderByExpression, bool IsDESC, bool? AsNoTracking = true, List<SortParms<T>> thenByExpression = null) where T : class, new();

        /// <summary>
        /// 返回指定条件的数据   最多返回一条
        /// </summary>
        /// <param name="specification"></param>
        /// <returns></returns>
        T GetByCondition<T>(ISpecification<T> specification, bool? AsNoTracking = false) where T : class, new();

        /// <summary>
        /// 返回指定标识的实体
        /// </summary>
        /// <param name="key">唯一标识</param>
        /// <returns></returns>
        T GetByKey<T>(object key) where T : class, new();

        /// <summary>
        /// 将实体数据保存到EF上下文中
        /// </summary>
        /// <param name="entity"></param>
        /// <returns></returns>
        void Add<T>(T entity) where T : class, new();

        /// <summary>
        /// 批量将实体数据保存到EF上下文中
        /// </summary>
        /// <param name="entity"></param>
        /// <returns></returns>
        void AddBatch<T>(IEnumerable<T> entities) where T : class, new();

        /// <summary>
        /// 更新数据EF上下文中的一条数据  根据主键值
        /// </summary>
        /// <param name="entity"></param>
        /// <returns></returns>
        void Modify<T>(T entity) where T : class, new();

        /// <summary>
        /// 更新实体的指定属性
        /// </summary>
        /// <param name="entity"></param>
        /// <param name="properties"></param>
        void Update<T>(T entity, params Expression<Func<T, object>>[] properties) where T : class, new();
        /// <summary>
        /// 逻辑删除
        /// </summary>
        /// <param name="specification"></param>
        void LogicDelete<T>(ISpecification<T> specification) where T : class, new();


        /// <summary>
        /// 从EF上下文中删除数据   仅用于同一上下文的集合对象有效
        /// </summary>
        /// <param name="entity"></param>
        /// <returns></returns>
        void Remove<T>(T entity) where T : class, new();
        /// <summary>
        /// 从EF上下文中删除数据   仅用于同一上下文的集合对象有效
        /// </summary>
        /// <param name="entity"></param>
        /// <returns></returns>
        void RemoveRange<T>(List<T> entity) where T : class, new();

        /// <summary>
        /// 删除指定条件的数据
        /// </summary>
        /// <param name="specification"></param>
        /// <returns></returns>
        void Remove<T>(ISpecification<T> specification) where T : class, new();

        /// <summary>
        /// 判断指定条件的数据是否存在
        /// </summary>
        /// <param name="specification"></param>
        /// <returns></returns>
        bool Exists<T>(ISpecification<T> specification) where T : class, new();
        /// <summary>
        /// 获取DB实列
        /// </summary>
        /// <returns></returns>
        Entities DbContext();
        /// <summary>
        /// 分页获取数据
        /// </summary>
        /// <typeparam name="M"></typeparam>
        /// <param name="query"></param>
        /// <param name="PageIndex"></param>
        /// <param name="PageSize"></param>
        /// <param name="AsNoTracking"></param>
        /// <param name="thenByExpression"></param>
        /// <returns></returns>
        EntityList<M> FindAllAsQuery<M>(IQueryable<M> query, int PageIndex, int PageSize, bool? AsNoTracking = true, List<SortParms<M>> thenByExpression = null) where M : class, new();
        EntityList<M> FindAllAsQueryExport<M>(IQueryable<M> query, int PageIndex, int PageSize, bool? AsNoTracking = true, List<SortParms<M>> thenByExpression = null) where M : class, new();

        /// <summary>
        /// 排序
        /// </summary>
        /// <typeparam name="M"></typeparam>
        /// <param name="source"></param>
        /// <param name="sort"></param>
        /// <returns></returns>
        IOrderedQueryable<M> DataSort<M>(IQueryable<M> source, Dictionary<string, string> sort) where M : class, new();
        bool SaveChanges();
        void Dispose();
        Task<bool> SaveChangesAsync();
        /// <summary>
        /// 获取所有数据
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="query"></param>
        /// <param name="PageIndex"></param>
        /// <param name="PageSize"></param>
        /// <returns></returns>
        EntityList<T> FindAllAsQueryPage<T>(IQueryable<T> query, int PageIndex, int PageSize) where T : class, new();

        #endregion
    }
}
